package com.jn.touchdemo.views;

import android.content.Context;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
import android.view.animation.RotateAnimation;
import android.widget.AbsListView;
import android.widget.ImageView;
import android.widget.ListView;
import android.widget.ProgressBar;
import android.widget.TextView;

import com.jn.touchdemo.R;

public class RefreshListView extends ListView {
   private static final float DAMPING_FACTOR = 0.5f;
   private View headerView;
   private float downY;
   private int headerViewHeight;
   private float offsetY;
   private static final int STATE_PULL_TO_REFRESH = 0;
   private static final int STATE_RELEASE_REFRESH = 1;
   private static final int STATE_REFRESHING = 2;
   private static final int STATE_RELEASE_LOADMORE = 3;
   private int currentState = STATE_PULL_TO_REFRESH;
   private ImageView iv_arrow;
   private ProgressBar progress_bar;
   private TextView tv_state;
   private RotateAnimation upAnim;
   private RotateAnimation downAnim;
   private OnRefreshingListener mOnRefreshingListener;
   private View footerView;
   private int footerViewHeight;
   private boolean loadingMore;

   public RefreshListView(Context context, AttributeSet attrs) {
      super(context, attrs);
      initHeaderView();
      initFooterView();
   }

   private void initHeaderView() {
      headerView = View.inflate(getContext(), R.layout.header_view, null);
      iv_arrow = (ImageView) headerView.findViewById(R.id.iv_arrow);
      progress_bar = (ProgressBar) headerView.findViewById(R.id.progress_bar);
      showRefreshingProgressBar(false);
      tv_state = (TextView) headerView.findViewById(R.id.tv_state);
      headerView.measure(0, 0);
      headerViewHeight = headerView.getMeasuredHeight();
      hideHeaderView();
      addHeaderView(headerView);
      upAnim = createRotateAnim(0f, -180f);
      downAnim = createRotateAnim(-180f, -360f);
   }

   private void initFooterView() {
      footerView = View.inflate(getContext(), R.layout.footer_view, null);
      footerView.measure(0, 0);
      footerViewHeight = footerView.getMeasuredHeight();
      hideFooterView();
      addFooterView(footerView);
   }

   private void hideFooterView() {
      int paddingTop = -footerViewHeight;
      setFooterViewPaddingTop(paddingTop);
   }

   private void showFooterView() {
      int paddingTop = 0;
      setFooterViewPaddingTop(paddingTop);
   }

   private void setFooterViewPaddingTop(int paddingTop) {
      footerView.setPadding(0, paddingTop, 0, 0);
   }

   private void showRefreshingProgressBar(boolean showProgressBar) {
      progress_bar.setVisibility(showProgressBar ? View.VISIBLE : View.GONE);
      iv_arrow.setVisibility(!showProgressBar ? View.VISIBLE : View.GONE);
      if (showProgressBar) {
         iv_arrow.clearAnimation();  // 有动画的View要清除动画才能真正的隐藏
      }
   }

   private RotateAnimation createRotateAnim(float fromDegrees, float toDegrees) {
      int pivotXType = RotateAnimation.RELATIVE_TO_SELF;    // 旋转点的参照物
      int pivotYType = RotateAnimation.RELATIVE_TO_SELF;    // 旋转点的参照物
      float pivotXValue = 0.5f;  // 旋转点x方向的位置
      float pivotYValue = 0.5f;  // 旋转点y方向的位置
      RotateAnimation ra = new RotateAnimation(fromDegrees, toDegrees, pivotXType, pivotXValue, pivotYType, pivotYValue);
      ra.setDuration(300);
      ra.setFillAfter(true);  // 让动画停留在结束位置
      return ra;
   }

   private void hideHeaderView() {
      int paddingTop = -headerViewHeight;
      setHeaderViewPaddingTop(paddingTop);
   }

   private void showHeaderView() {
      int paddingTop = 0;
      setHeaderViewPaddingTop(paddingTop);
   }

   private void setHeaderViewPaddingTop(int paddingTop) {
      headerView.setPadding(0, paddingTop, 0, 0);
   }

   @Override
   public boolean onTouchEvent(MotionEvent ev) {
      Log.d("asdf", "-----------------" + ev.getAction());
      switch (ev.getAction()) {
         case MotionEvent.ACTION_DOWN:
            downY = ev.getY();
            break;
         case MotionEvent.ACTION_MOVE:
            if (currentState == STATE_REFRESHING) {
               // 如果当前已经是“正在刷新”的状态了，则不用去处理下拉刷新了
               return super.onTouchEvent(ev);
            }
            int fingerMoveDistanceY = (int) (ev.getY() - downY);    // 手指移动的距离
            if (fingerMoveDistanceY > 0 && getFirstVisiblePosition() == 0) {
               // 应用阻尼效果
               int dampedDistance = (int) (fingerMoveDistanceY * DAMPING_FACTOR);
               int paddingTop = -headerViewHeight + dampedDistance;
               setHeaderViewPaddingTop(paddingTop);

               if (paddingTop < 0 && currentState != STATE_PULL_TO_REFRESH) {
                  // 如果paddingTop小于0，说明HeaderView没有完全显示出来，则进入下拉刷新的状态
                  currentState = STATE_PULL_TO_REFRESH;
                  tv_state.setText("下拉刷新");
                  iv_arrow.startAnimation(downAnim);
                  showRefreshingProgressBar(false);
                  // 让箭头转一下
               } else if (paddingTop >= 0 && currentState != STATE_RELEASE_REFRESH) {
                  // 如果paddingTop>=0，说明HeaderView已经完全显示出来，则进入松开刷新的状态
                  currentState = STATE_RELEASE_REFRESH;
                  tv_state.setText("松开刷新");
                  iv_arrow.startAnimation(upAnim);
                  showRefreshingProgressBar(false);
               }
               return true;
            } else if (fingerMoveDistanceY < 0 && getLastVisiblePosition() == getCount() - 1 && !loadingMore) {
               currentState = STATE_RELEASE_LOADMORE;
               int paddingTop = footerViewHeight + fingerMoveDistanceY;
               setFooterViewPaddingTop(-paddingTop);
            }
            break;
         case MotionEvent.ACTION_UP:
            if (currentState == STATE_RELEASE_REFRESH) {
               // 如果当前状态是松开刷新，并且抬起了手，则进入正在刷新状态
               currentState = STATE_REFRESHING;
               tv_state.setText("正在刷新");
               showRefreshingProgressBar(true);
               showHeaderView();
               if (mOnRefreshingListener != null) {
                  mOnRefreshingListener.onRefreshing();
               }
            } else if (currentState == STATE_PULL_TO_REFRESH) {
               // 如果抬起手时是下拉刷新状态，则把HeaderView完成隐藏
               hideHeaderView();
            } else if (currentState == STATE_RELEASE_LOADMORE) {
               loadingMore = true;
               showFooterView();
               setSelection(getCount() - 1);
               if (mOnRefreshingListener != null) {
                  mOnRefreshingListener.onLoadMore();
               }
               currentState = STATE_PULL_TO_REFRESH;
            }
            break;
      }
      return super.onTouchEvent(ev);
   }

   public void setOnRefreshingListener(OnRefreshingListener mOnRefreshingListener) {
      this.mOnRefreshingListener = mOnRefreshingListener;
   }

   public interface OnRefreshingListener {
      void onRefreshing();
      void onLoadMore();
   }

   public void onRefreshComplete() {
      hideHeaderView();
      currentState = STATE_PULL_TO_REFRESH;
      showRefreshingProgressBar(false);
   }

   public void onLoadmoreComplete() {
      hideFooterView();
      loadingMore = false;
      setSelection(getCount() - 1);
   }

   public void notifyDataChange() {
      setSelection(getCount() - 1);
   }
}